﻿using System;

namespace InDepth2Demo.Chapter4
{
    // 4.2.2 + 4.2.3
    // Boxing and unboxing behaivor of nullable types
    // Nullable<T>装箱和拆箱
    internal class BoxAndUnboxOfNullable
    {
        public static void Call()
        {
            Nullable<int> nullable = 5;
            Console.WriteLine(nullable.GetType());          //System.Int32

            // 装箱成“有值的可空类型的实例” 
            object boxed = nullable;                        // 对有值的 int? 装箱                    
            Console.WriteLine(boxed.GetType());             //System.Int32

            //拆箱成非可空变量
            int normal = (int)boxed;                        // 装箱后可以拆箱成 int
            Console.WriteLine(normal);                      //5

            //拆箱成可空变量
            nullable = (Nullable<int>)boxed;                // 装箱后也可以拆箱成 int?
            Console.WriteLine(nullable);                    //5

            //装箱成“没有值的可空类型的实例”
            nullable = new Nullable<int>();
            boxed = nullable;                               // 对没有值的 int? 装箱
            Console.WriteLine(boxed == null);               //True  ，即返回的是一个 null        

            //拆箱成可空变量
            nullable = (Nullable<int>)boxed;                // 装箱后也可以拆箱成 int? , 但不能拆箱成 int
            Console.WriteLine(nullable.HasValue);           //False
        }
        // 程序证明了为了获取值，既可以拆箱成 int，又可以拆箱成 Nullable<int>。
        // 最后输出结果证明了可以将 “一个没有值的可空类型的实例” 装箱成空引用，然后成功拆箱成另一个没有值的可空实例。
        // 如果企图将 boxed 的最后一个值拆箱成非可空的 int，程序会抛出一个 NullReferenceException。


        // 4.2.3 Nullable<T>实例的相等性
        static void Call2()
        {
            // 调用 first.Equals(second) 的具体规则
        }

        //public override bool Equals(object other)
        //{
        //    if (!hasValue)                        // 没有值
        //    {
        //        return other == null;                 // 如果first没有值，second为 null，它们就是相等的;    second不为 null，它们就是不相等的;
        //    }
        //    if (other == null)                    // 有值
        //    {
        //        return false;                         // first 有值，second为 null，它们就是不相等的;
        //    }
        //    return value.Equals(other);               // 否则，如果 first 的值等于 second，它们就是相等的。
        //}

        //如果first没有值，second为 null，它们就是相等的;
        //如果£irst没有值，second不为 null，它们就是不相等的;
        //如果first有一个值，second为 null，它们就是不相等的;
        //否则，如果first的值等于second，它们就是相等的。


    }
}
